package de.osflex.touarek.desktop
{
	import de.osflex.touarek.containers.DragPanel;
	import de.osflex.touarek.containers.HTMLContainer;
	import de.osflex.touarek.containers.SuperApplicationControlBar;
	import de.osflex.touarek.util.Config;
	
	import flash.display.NativeWindow;
	import flash.display.Screen;
	import flash.events.Event;
	import flash.events.EventDispatcher;
	import flash.events.IEventDispatcher;
	import flash.events.MouseEvent;
	import flash.net.NetConnection;
	import flash.net.Responder;
	
	import mx.containers.Form;
	import mx.containers.FormItem;
	import mx.containers.TitleWindow;
	import mx.controls.Alert;
	import mx.controls.Button;
	import mx.controls.ComboBox;
	import mx.controls.HSlider;
	import mx.controls.Image;
	import mx.controls.Label;
	import mx.controls.LinkButton;
	import mx.controls.TextInput;
	import mx.core.WindowedApplication;
	import mx.events.CloseEvent;
	import mx.events.DropdownEvent;
	import mx.events.FlexEvent;
	import mx.events.SliderEvent;
	import mx.managers.PopUpManager;
	
	/**
	 * @author amoerke
	 * @created 20081105
	 * @class TouarekApplication
	 * 
	 * This class represents the main desktopapplication in the mxml-file
	 * it contains all functionality of the desktopapplication
	 */
		

	public class TouarekApplication extends EventDispatcher
	{
		private var _parent:WindowedApplication;
		private var _nativeWindow:NativeWindow;
		private var _htmlControl:HTMLContainer;
		private var _runtime:Object;
		private var _internalWidth:int = 0;
		private var _internalHeight:int = 0;	
		private var _applicationControlBar:SuperApplicationControlBar;
		private var _pnlMapContainer:DragPanel;	
		private var _pnlControlContainer:DragPanel;
		private var _pnlInfoContainer:DragPanel;
		private var _tiLocation:TextInput;
		private var _cbType:ComboBox;
		private var _arrComboDataProvider:Array;
		private var _sldDistance:HSlider;
		private var _service:NetConnection;
		private var _mapPosition:Array;
		private var _lblCompany:Label;
		private var _lblAdress:Label;
		private var _lblPhone:Label;
		private var _lblURL:Label;
		private var _lnkButton:LinkButton;
		private var _image:Image;
		private var _strAdress:String = '';
		private var _strPhone:String = '';
		private var _strCompany:String = '';
		private var _strURL:String = '';
		private var _window:TitleWindow;
		private var _arrCompanys:Array;
		private var _strCompanyName:String = '';
		private var _strCompanyAdress:String = '';
		private var _strCompanyPhone:String = '';
		private var _strCompanyURL:String = '';
		private var _strImageURL:String = '';		
		private var _pic:Image;		
		[Embed(source="assets/symbol.png")]
		private var symbolIcon:Class;	
		
		/**
		 * The constructor receives all necessary from the mxml
		 * to couple all funcionality to the WindowedApplication
		 * 
		 * @param p_parent:WindowedApplication
		 * @param target:IEventDispatcher
		 * 
		 */ 		
				
		public function TouarekApplication(p_parent:WindowedApplication, target:IEventDispatcher=null)
		{
			super(target);
			this._parent = p_parent;
			this._nativeWindow = p_parent.nativeWindow;
			this._runtime = this._parent;			
			this.init();
		}	 
		
		/**
		 * Lays the internal function to receive datas from 
		 * the webapplication on the server in the webapps hands
		 * 
		 * @see Touarek.mxml
		 */
		
		public function getSendFunction():Function
		{
			return this.internalFunctionToSend;
		}
		
		/**
		 * Setup the Window and htmlControl after creating
		 */
		
		protected function init():void
		{
			this._htmlControl = new HTMLContainer(this._runtime);
			this._parent.maximize();
			this._parent.addEventListener(FlexEvent.APPLICATION_COMPLETE, completeHandler);
			this._arrCompanys = new Array();			
		}
		
		/**
		 * Initialize the mandatory classvariables with applicationvalues
		 * after the APPLICATION_COMPLETE has been fired and start
		 * creating all components  for this application
		 * 
		 * @param event FlexEvent
		 */
		
		protected function completeHandler(event:FlexEvent):void
		{
			this._internalWidth = this._nativeWindow.width;
			this._internalHeight = this._nativeWindow.height;
			this._arrComboDataProvider = new Array();
			this._arrComboDataProvider.push({label:'Autos', data:Config.CAR});
			this._arrComboDataProvider.push({label:'Friseure', data:Config.HAIR});
			this.initComponents();					
							
		}
		
		/**
		 * Create all Components
		 */
		
		protected function initComponents():void
		{
			// ApplicationLabel
			var lblApplication:Label = new Label();
				lblApplication.text = Config.APPLICATION_NAME;
			
			// ApplicationControlBar
			this._applicationControlBar = new SuperApplicationControlBar();
			this._applicationControlBar.showControls = true;
			this._applicationControlBar.controlsRightDistance = 10;
			this._applicationControlBar.trayButtonVisible = false;
			this._applicationControlBar.id = 't_applicationBar';
			this._applicationControlBar.x = 0;
			this._applicationControlBar.y = 0;
			this._applicationControlBar.percentWidth = 100;
			this._applicationControlBar.height = 30;
			this._applicationControlBar.addChild(lblApplication);
			this._parent.addChild(this._applicationControlBar);
			
			// MapContainerPanel	
			this._pnlMapContainer = new DragPanel();		
			this._pnlMapContainer.id = 'mapContainer';
			this._pnlMapContainer.title = Config.MAP_WINDOW_NAME;
			this._pnlMapContainer.x = 5;
			this._pnlMapContainer.y = 35;
			this._pnlMapContainer.width = Math.round((this._internalWidth / 3) * 2 - 5);
			this._pnlMapContainer.height = Math.round(this._internalHeight-60);
			this._pnlMapContainer.isMainPanel = false;
			this._pnlMapContainer.verticalScrollPolicy = 'off';
			this._pnlMapContainer.horizontalScrollPolicy = 'off';
			this._pnlMapContainer.addChild(this._htmlControl);
			this._parent.addChild(this._pnlMapContainer);			
			
			// ControlPanel
			this._pnlControlContainer = new DragPanel();
			this._pnlControlContainer.id = 'controlPanel';
			this._pnlControlContainer.title = Config.CONTROL_WINDOW_NAME;
			this._pnlControlContainer.x = Math.round((this._internalWidth / 3) * 2 + 5);
			this._pnlControlContainer.y = 35;
			this._pnlControlContainer.width = Math.round((this._internalWidth / 3)-30);
			this._pnlControlContainer.height = 384;
			this._pnlControlContainer.horizontalScrollPolicy = 'off';
			this._pnlControlContainer.setStyle('backgroundColor', Config.PANEL_COLOR);
			this._pnlControlContainer.isMainPanel = false;
			
			// ControlPanel -> Form
			var form:Form = new Form();
			form.setStyle('verticalGap', 15);
			var formItemLoc:FormItem = new FormItem();
			formItemLoc.label = 'Ort/PLZ:';
			this._tiLocation = new TextInput();
			this._tiLocation.id = 'location';
			this._tiLocation.addEventListener(FlexEvent.ENTER, enterListener);
			formItemLoc.addChild(this._tiLocation);
			form.addChild(formItemLoc);
			var formItemType:FormItem = new FormItem();
			formItemType.label = 'Firma:';
			this._cbType = new ComboBox();
			this._cbType.id = 'cbType';
			this._cbType.width = 160;
			this._cbType.dataProvider = this._arrComboDataProvider;
			this._cbType.addEventListener(DropdownEvent.CLOSE, sendCompanySearchToWeb);
			formItemType.addChild(this._cbType);
			form.addChild(formItemType);
			var formItemDistance:FormItem = new FormItem();
			formItemDistance.label = 'Distanz(km):';
			this._sldDistance = new HSlider();
			this._sldDistance.tickInterval = 5;
			this._sldDistance.minimum = 5;
			this._sldDistance.maximum = 50;
			this._sldDistance.snapInterval = 5;
			this._sldDistance.tickValues = [5, 10, 15, 20, 25, 30, 35, 40, 45, 50];
			this._sldDistance.labels = ['', 10, '', 20, '', 30, '', 40, '', 50 ];
			this._sldDistance.addEventListener(SliderEvent.CHANGE, changeRadius);
			formItemDistance.addChild(this._sldDistance);
			form.addChild(formItemDistance);
			var formItemButton:FormItem = new FormItem();
			var btnSearch:Button = new Button();
			btnSearch.label = 'suchen';
			btnSearch.addEventListener(MouseEvent.CLICK, sendCompanySearchToWeb);
			formItemButton.addChild(btnSearch);
			form.addChild(formItemButton);
			this._pnlControlContainer.addChild(form);
			this._parent.addChild(this._pnlControlContainer);			
			
			// InfoPanel
			this._pnlInfoContainer = new DragPanel();
			this._pnlInfoContainer.title = Config.INFO_WINDOW_NAME;
			this._pnlInfoContainer.x = Math.round((this._internalWidth / 3) * 2 + 5);
			this._pnlInfoContainer.y = this._pnlControlContainer.y + this._pnlControlContainer.height + 5
			this._pnlInfoContainer.width = Math.round((this._internalWidth / 3)-30);
			this._pnlInfoContainer.height = this._internalHeight - (35 + 384) - 35;
			this._pnlInfoContainer.setStyle('backgroundColor', Config.PANEL_COLOR);
			this._pnlInfoContainer.isMainPanel = false;
			var infoForm:Form = new Form();
			infoForm.setStyle('paddingLeft', 1);
			
			var formItemCompany:FormItem = new FormItem();
			formItemCompany.label = 'Firma:';
			this._lblCompany = new Label();
			this._lblCompany.text = this._strCompany;
			formItemCompany.addChild(this._lblCompany);
			infoForm.addChild(formItemCompany);
			
			var formItemAdress:FormItem = new FormItem();
			formItemAdress.label = 'Adresse:';
			this._lblAdress = new Label();
			this._lblAdress.text = this._strAdress;
			formItemAdress.addChild(this._lblAdress);
			infoForm.addChild(formItemAdress);
			
			var formItemPhone:FormItem = new FormItem();
			formItemPhone.label = 'Telefon:';
			this._lblPhone = new Label();
			this._lblPhone.text = this._strPhone;
			formItemPhone.addChild(this._lblPhone);
			infoForm.addChild(formItemPhone);
			
			var formItemURL:FormItem = new FormItem();
			formItemURL.label = 'URL:';
			this._lnkButton = new LinkButton();			
			this._lnkButton.label = this._strURL;			
			this._lnkButton.addEventListener(MouseEvent.CLICK, visitURL);
			formItemURL.addChild(this._lnkButton);
			infoForm.addChild(formItemURL);			
						
			var formItemImage:FormItem = new FormItem();
			formItemImage.label = 'Logo:';
			this._pic = new Image();
			//this._pic.load(this._strImageURL);
			formItemImage.addChild(this._pic);
			infoForm.addChild(formItemImage);
			this._pnlInfoContainer.addChild(infoForm);			
			this._parent.addChild(_pnlInfoContainer);		
		}		
		
		
		/**
		 * Clickhandler for the URL-Button of the infowindow
		 * It initializes the BrowserWindow with the custom HTMLControl
		 * 
		 * @param event MouseEvent
		 */
		
		
		protected function visitURL(event:MouseEvent):void
		{		
			var htmlCompControl:HTMLContainer = new HTMLContainer(new Object(), this._strURL);
			_window = TitleWindow(PopUpManager.createPopUp(this._parent,TitleWindow,true));
			_window.height = Screen.mainScreen.bounds.height - 100;
			_window.width = Screen.mainScreen.bounds.width - 50;
			_window.verticalScrollPolicy = 'auto';
			_window.title = Config.URL_BROWSER_TITLE
			_window.showCloseButton = true;				
			_window.addChild(htmlCompControl);												
			_window.addEventListener(CloseEvent.CLOSE, closeHandler);			
			htmlCompControl.location = event.currentTarget.label;
			htmlCompControl.verticalScrollPolicy = 'auto';
			htmlCompControl.horizontalScrollPolicy = 'off';
			htmlCompControl.userAgent = 'Mozilla/5.0 (X11; U; Linux i686; en;) AppleWebKit/522.15.5 (KHTML, like Gecko) Version/3.0.3 Safari/522.15.5';
			htmlCompControl.htmlLoader.navigateInSystemBrowser = false;
			htmlCompControl.htmlLoader.useCache = true;			 	
		}
		
		/**
		 * The closehandler of the BrowserWindow
		 * 
		 * @param event CloseEvent
		 */
		
		protected function closeHandler(event:CloseEvent):void{
			PopUpManager.removePopUp(_window);
		}
		
		/**
		 * Changehandler of the Distanceslider
		 * makes sure that a new search will be started
		 * @param event SliderEvent
		 */
		 
		protected function changeRadius(event:SliderEvent):void
		{				
			this.sendCompanySearchToWeb();
		}
		
		/**
		 * The listener for the enterevent of the Searchtextinput
		 * wich starts a new companysearch
		 * 
		 * @param event FlexEvent		  
		 */
		
		private function enterListener(event:FlexEvent):void
		{
			this._htmlControl.domWindow.sendToTouarekWebApp('doGeocode', event.currentTarget.text);
		}
		
		/**
		 * This function is connected via javascript with the webapplication on
		 * the Server
		 * 
		 * @param type String
		 * @param _value *
		 * @param _value2 *
		 */
		
		public function internalFunctionToSend(type:String, _value:*, _value2:*):void
		{			
			switch(type){
				case 'showInfo':
					this.fillDatasToInfoPanel(Number(_value));		
				break;
				case 'getMapPosition':
					this.getMapPosition(_value, _value2);
				break;
				case 'mapInitComplete':
					this.mapInitComplete();
				break;
			}
		}	
		
		/**
		 * Starts a companysearch for the current pane in the mapwindow
		 */
		
		private function mapInitComplete():void
		{
			this.sendCompanySearchToWeb();
		}
		
		/**
		 * After click on a marker in the map the infopanel has to be filled
		 * with the companydata of the current marker
		 * @param _id Number
		 */
		
		protected function fillDatasToInfoPanel(_id:Number):void
		{
			for(var i:uint=0; i<this._arrCompanys.length; i++){
				if(this._arrCompanys[i].id == _id){
					this._lblCompany.text = this._arrCompanys[i].company_name;
					this._lblAdress.text = this._arrCompanys[i].adress;
					this._lblPhone.text = this._arrCompanys[i].telefon;
					this._lnkButton.label = this._arrCompanys[i].url;
					this._strImageURL = 'http://www.osflex.de/geo/touarek/requestHandler.php?id='+this._arrCompanys[i].id;						
					this._pic.load(this._strImageURL);
					if(this._arrCompanys[i].url == 'Keine Webseite'){
						this._lnkButton.enabled = false;
					}else{
						this._lnkButton.enabled = true;
					}						
					break;
				}
			}			
		}
		
		/**
		 * Sends the searchevent to the webapplication
		 * @param event Event
		 */
		
		protected function sendCompanySearchToWeb(event:Event=null):void
		{				
			
			this._htmlControl.domWindow.sendToTouarekWebApp(	'doSearch', 
														this._cbType.selectedItem.data,
														this._sldDistance.value
														);
			var arrTmp:Array = new Array();
			arrTmp['type'] = this._cbType.selectedItem.data;
			arrTmp['latlng'] = this._mapPosition;
			arrTmp['distance'] = this._sldDistance.value;											
			this._service = new NetConnection();
			this._service.connect(Config.GATEWAY_LOCATION);
			this._service.call(	'SearchController.searchCompany', 
								new Responder(handleSearchResults), 
								arrTmp);
		}
		
		/**
		 * Prepares an array with the current MapCenterPosition
		 * called from the webapplication
		 * 
		 * @param _value Number
		 * @param _value2 Number
		 */
		
		protected function getMapPosition(_value:Number, _value2:Number):void
		{				
			this._mapPosition = new Array();
			this._mapPosition[0] = _value;
			this._mapPosition[1] = _value2;				
		}
		
		/**
		 * If the result contains companydata, the companyarray will be filled
		 * with it otherwise an Alertbox will be shown
		 * 
		 * @param _arrResponse Array
		 */
		
		protected function handleSearchResults(_arrResponse:Array):void
		{
			this._arrCompanys = _arrResponse;	
			if(this._arrCompanys.length < 1){
				Alert.show(	'Keine Ergebnisse gefunden!', 
							'Info', 
							Alert.OK, 
							this._parent, 
							null,  
							symbolIcon);
			}
		}		
	}
}